
#include <string>
#include <fstream>

#include "ChooseTextureWindow.h"

#include "../GLRenderer.h"
#include "globals.h"

using namespace std;


ChooseTextureWindow::ChooseTextureWindow() : MyBaseWindow( "Textures", 400, 460, BLUR_BEHIND | CLOSABLE ),
												prev_page_btn_("<", -0.25f, -0.97f, 0.245f, 0.1f, window_size_),
												next_page_btn_(">", 0.05f, -0.97f, 0.245f, 0.1f, window_size_){
	
	//SetWindowPos( window_handle_, HWND_TOPMOST, 0, 400, 0, 0, SWP_NOSIZE);
	//this->SetTopMost();

	//prev_page_btn_.reset( new MyButton("<", -0.25f, -0.97f, 0.245f, 0.1f, window_size_) );
	prev_page_slot_.AssignFunction(this, &ChooseTextureWindow::PrevPage);
	prev_page_slot_.Connect(prev_page_btn_.press_signal());
	//next_page_btn_.reset( new MyButton(">", 0.05f, -0.97f, 0.245f, 0.1f, window_size_) );
	next_page_slot_.AssignFunction(this, &ChooseTextureWindow::NextPage);
	next_page_slot_.Connect(next_page_btn_.press_signal());

	texture_list_.reserve(256);
	ifstream tex_stream("textures/texture_list.txt");
	string str;

	while(getline(tex_stream, str))
	{
		str.erase(std::remove(str.begin(), str.end(), '\r'), str.end());
		texture_list_.push_back(str);
		cout << str << endl;
	}
	texture_list_.shrink_to_fit();

	tex_pos_ = 0;
	num_cur_textures_ = 0;

	for( auto tex_it = texture_list_.begin(); tex_it != texture_list_.end(); tex_it++ )
	{
		int ndx = tex_it - texture_list_.begin();
		if(ndx >= 16)
		{
			break;
		}
		cur_textures_[ndx] = Renderer::LoadTGATexture((*tex_it).c_str());
		num_cur_textures_++;
	}

	selection_ = -1;

	update_needed_ = true;
	OnMove(0.0f, 0.0f);
}

ChooseTextureWindow::~ChooseTextureWindow() {

	Renderer::DeleteOwnTextures(num_cur_textures_, cur_textures_);

}

int ChooseTextureWindow::OnClick(float x, float y){

	if( MyBaseWindow::OnClick(x, y) == -1 )
	{
		return -1;
	}

	prev_page_btn_.Check(x, y);
	next_page_btn_.Check(x, y);

	float new_x = ((x * 400.0f*0.5f) - 0.0f)/(400.0f*0.5f);
	float new_y = ((y * 460.0f*0.5f) - 0.0f)/(400.0f*0.5f);

	for(unsigned int i = 0; i < 4; i++)
	{
		for(unsigned int j = 0; j < 4; j++)
		{
			if(i*4+j>=num_cur_textures_)
			{
				goto EXIT;
			}
			float quad_dims[] = {	-1.0f+0.02f+(0.02f+0.475f)*j,			1.0f-0.02f-(0.02f+0.475f)*i,
									-1.0f+0.02f+(0.02f+0.475f)*j+0.475f,	1.0f-0.02f-(0.02f+0.475f)*i-0.475f	};
			if(new_x > quad_dims[0] && new_x < quad_dims[2])
			{
				if(new_y > quad_dims[3] && new_y < quad_dims[1])
				{
					selection_ = tex_pos_ + i*4+j;
					goto EXIT;
				}
			}

		}
	}
	EXIT:

	return 0;
}

int ChooseTextureWindow::OnRelease(float x, float y) {

	if(MyBaseWindow::OnRelease(x, y) == -1)
	{
		return -1;
	}

	prev_page_btn_.Check(x, y);
	next_page_btn_.Check(x, y);

	if(selection_ == -1)
	{
		return 0;
	}

	float new_x = ((x * 400.0f*0.5f) - 0.0f)/(400.0f*0.5f);
	float new_y = ((y * 460.0f*0.5f) - 0.0f)/(400.0f*0.5f);

	for(unsigned int i = 0; i < 4; i++)
	{
		for(unsigned int j = 0; j < 4; j++)
		{
			if(i*4+j>=num_cur_textures_)
			{
				goto EXIT;
			}
			float quad_dims[] = {	-1.0f+0.02f+(0.02f+0.475f)*j,			1.0f-0.02f-(0.02f+0.475f)*i, 
									-1.0f+0.02f+(0.02f+0.475f)*j+0.475f,	1.0f-0.02f-(0.02f+0.475f)*i-0.475f	};

			if(new_x > quad_dims[0] && new_x < quad_dims[2])
			{
				if(new_y > quad_dims[3] && new_y < quad_dims[1])
				{
					selection_ = tex_pos_ + i*4+j;
					goto EXIT;
				}
			}

		}
	}
	EXIT:

	if(selection_ != -1)
	{
		shared_ptr<GLTexture> tex = Renderer::LoadTexture2(texture_list_[tex_pos_ + selection_].c_str());
		g_selection_frame->SetTexrure(tex);
		selection_ = -1;
		this->Hide();
	}

	cout << x << " " << y << " " << selection_ << endl;

	return 0;
}

void ChooseTextureWindow::Draw() {
	
	MyBaseWindow::Draw();
	this->SetTopMost();
	
	prev_page_btn_.Draw();
	next_page_btn_.Draw();

	glEnable(GL_BLEND);

	glDisable(GL_CULL_FACE);
	glDisable(GL_DEPTH_TEST);
	Renderer::CheckGLError("BeforeDraw");
	glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);

	Renderer::SetViewport( 0, 30, 400, 400);

	for(unsigned int i = 0; i < 4; i++)
	{
	for(unsigned int j = 0; j < 4; j++)
	{
		if(i*4+j >= num_cur_textures_)
		{
			//goto EXIT;
			return;
		}
		Renderer::SwitchOwnTexture( DIFFUSEMAP_SLOT, cur_textures_[i*4+j] );

		float quad_vtx[] = {	-1.0f+0.02f+(0.02f+0.475f)*j,			1.0f-0.02f-(0.02f+0.475f)*i, 0.0f, 
								-1.0f+0.02f+(0.02f+0.475f)*j,			1.0f-0.02f-(0.02f+0.475f)*i-0.475f, 0.0f, 
								-1.0f+0.02f+(0.02f+0.475f)*j+0.475f,	1.0f-0.02f-(0.02f+0.475f)*i, 0.0f, 
								-1.0f+0.02f+(0.02f+0.475f)*j+0.475f,	1.0f-0.02f-(0.02f+0.475f)*i-0.475f, 0.0f	};
		float quad_tex[] = {0.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, 1.0f, 1.0f};

		glEnableVertexAttribArray(Renderer::render_state->current_program->attribute(POSITION_ATTRIBUTE));
		glVertexAttribPointer(Renderer::render_state->current_program->attribute(POSITION_ATTRIBUTE), 3, GL_FLOAT, GL_FALSE, 0, quad_vtx);

		glEnableVertexAttribArray(Renderer::render_state->current_program->attribute(UV_ATTRIBUTE));
		glVertexAttribPointer(Renderer::render_state->current_program->attribute(UV_ATTRIBUTE), 2, GL_FLOAT, GL_FALSE, 0, quad_tex);

		glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);

		glDisableVertexAttribArray(Renderer::render_state->current_program->attribute(UV_ATTRIBUTE));
		glDisableVertexAttribArray(Renderer::render_state->current_program->attribute(POSITION_ATTRIBUTE));
	}
	}
//EXIT:
	//int y;
}

int ChooseTextureWindow::PrevPage() {

	if(tex_pos_>=16)
	{
		tex_pos_ -= 16;
	}

	Renderer::DeleteOwnTextures(num_cur_textures_, cur_textures_);

	num_cur_textures_ = 0;
	for( auto tex_it = texture_list_.begin() + tex_pos_; tex_it != texture_list_.end(); tex_it++ )
	{
		int ndx = tex_it - texture_list_.begin() - tex_pos_;
		if(ndx >= 16)
		{
			break;
		}
		cur_textures_[ndx] = Renderer::LoadTGATexture((*tex_it).c_str());
		num_cur_textures_++;
	}
	return 0;
}

int ChooseTextureWindow::NextPage() {
	if(tex_pos_<texture_list_.size()-16)
	{
		tex_pos_ += 16;
	}

	Renderer::DeleteOwnTextures(num_cur_textures_, cur_textures_);

	num_cur_textures_ = 0;
	for( auto tex_it = texture_list_.begin() + tex_pos_; tex_it != texture_list_.end(); tex_it++ )
	{
		int ndx = tex_it - texture_list_.begin() - tex_pos_;
		if(ndx >= 16)
		{
			break;
		}
		cur_textures_[ndx] = Renderer::LoadTGATexture((*tex_it).c_str());
		num_cur_textures_++;
	}

	return 0;
}

/*
LRESULT ChooseTextureWindow::WndProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) {

	if( FireSignals( hWnd, message, wParam, click_signal, release_signal, move_signal ) )
	{
		//return DefWindowProc( hWnd, message, wParam, lParam );
	}

	switch( message )
	{
		case WM_KEYDOWN:
			break;
		case WM_KEYUP:
			break;
		case WM_MOUSEWHEEL:
			break;
		case WM_RBUTTONDOWN:
			break;
		case WM_RBUTTONUP:
			break;
	}


	return DefWindowProc( hWnd, message, wParam, lParam );
}
*/
